<template>
  <div class="app-container">
    <div class="">
      <el-form :inline="true" :model="listQuery">
        <el-row :gutter="20">
          <el-col :span="12">
            <el-form-item>
              <el-button v-waves type="primary" icon="el-icon-refresh" class="filter-item" @click="getList">刷新</el-button>
              <el-button v-if="treeDefaultExpand" v-waves type="primary" icon="el-icon-caret-top" class="filter-item" @click="clickSwitchExpand(false)">全部收起</el-button>
              <el-button v-else v-waves type="primary" icon="el-icon-caret-bottom" class="filter-item" @click="clickSwitchExpand(true)">全部展开</el-button>
            </el-form-item>
          </el-col>
          <el-col :span="12" style="display: flex;flex-direction: row-reverse">
            <el-form-item>
              <el-button v-permission="['action:system:permission:create']" v-waves type="primary" icon="el-icon-circle-plus-outline" class="filter-item" @click="clickCreate">新增权限项</el-button>
            </el-form-item>
          </el-col>
        </el-row>
      </el-form>
    </div>

    <el-table
      ref="refTreeTable"
      v-loading="listLoading"
      :header-cell-style="{ background:'#eef1f6',color:'#606266' }"
      border
      :data="tree"
      stripe
      row-key="id"
      :indent="20"
      :tree-props="{ children: 'children' }"
      :default-expand-all="treeDefaultExpand"
      @selection-change="handleSelectionChange"
    >
      <el-table-column fixed="left" label="权限名称" min-width="160px">
        <template v-slot="scope">
          <span>{{ scope.row.name }}</span>
        </template>
      </el-table-column>
      <el-table-column label="权限类型" prop="routes" width="100px">
        <template v-slot="scope">
          <el-tag :type="labelTypeClassMap[scope.row.type]" effect="plain" size="small">{{ labelTypeTextMap[scope.row.type] }}</el-tag>
        </template>
      </el-table-column>
      <el-table-column label="权限标识符" prop="routes" min-width="100px">
        <template v-slot="scope">
          <el-tooltip placement="top" effect="light">
            <div slot="content">
              {{ scope.row.code }}
            </div>
            <el-tag :type="labelTypeClassMap[scope.row.type]" effect="plain" size="mini" @click="handleCopy(scope.row.code, $event)">{{ scope.row.code }}</el-tag>
          </el-tooltip>
        </template>
      </el-table-column>
      <el-table-column label="排序" prop="sort" width="80px" />
      <el-table-column label="权限路由" prop="routes" min-width="500px">
        <template v-slot="scope">
          <el-tag v-for="(item,key) in jsonRoutes(scope.row.routes)" :key="key" :type="labelTypeClassMap[scope.row.type]" effect="plain" size="mini" style="margin: 0 5px 5px 0">
            {{ item }}
          </el-tag>
        </template>
      </el-table-column>
      <el-table-column fixed="right" label="操作" width="200px">
        <template v-slot="scope">
          <el-button v-permission="['action:system:permission:update']" v-waves type="primary" size="mini" icon="el-icon-edit-outline" @click="clickUpdate(scope.row)">编辑</el-button>
          <el-button v-permission="['action:system:permission:delete']" v-waves type="danger" size="mini" icon="el-icon-delete" @click="clickDelete(scope.row)">删除</el-button>
        </template>
      </el-table-column>
    </el-table>

    <!-- 新增|编辑用户弹窗 -->
    <el-drawer
      ref="drawer"
      :title="formTitle"
      :visible.sync="formVisible"
      :close-on-press-escape="false"
      :wrapper-closable="false"
      :destroy-on-close="true"
      :with-header="true"
      size="50%"
      direction="rtl"
    >
      <div class="drawer-main" style="padding: 0 20px 0 20px;">
        <div class="drawer-main-content">
          <el-form ref="refForm" :model="form" :rules="rules" label-position="top" label-width="120px">
            <el-form-item label="权限类型" prop="type">
              <el-radio-group v-model="form.type">
                <el-radio-button :label="1">菜单栏</el-radio-button>
                <el-radio-button :label="2">按钮</el-radio-button>
              </el-radio-group>
            </el-form-item>
            <el-form-item label="" prop="parent_id">
              <template slot="label">
                上级权限
                <el-tag v-if="parentNode.code" effect="plain" size="mini" title="点击可复制CODE" @click="handleCopy(parentNode.code, $event)">{{ parentNode.name }} - {{ parentNode.code }}</el-tag>
              </template>
              <el-cascader ref="cascader" v-model="form.parent_id" :options="tree" :props="{emitPath: false, value: 'id', label: 'name', checkStrictly: true}" filterable clearable style="width: 100%" @change="cascaderChange">
                <template v-slot="{ node, data }">
                  <span style="float: left;margin-right: 20px;">{{ data.name }}</span>
                  <span style="float: right; color: #8492a6; font-size: 13px">{{ data.code }}</span>
                </template>
              </el-cascader>
            </el-form-item>
            <el-form-item label="权限名称" prop="name">
              <el-input v-model.trim="form.name" clearable />
            </el-form-item>
            <el-form-item label="标识符" prop="code">
              <template slot="label">
                标识符
                <el-tooltip class="item" effect="dark" content="按钮权限标识符推荐以【action】作为前缀 [示例[新增角色按钮 action:system:role:create]]" placement="bottom-start">
                  <i class="el-icon-question" />
                </el-tooltip>
              </template>
              <el-input v-model.trim="form.code" clearable />
            </el-form-item>
            <el-form-item label="排序" prop="sort">
              <el-input v-model.number="form.sort" type="number" min="0" clearable />
            </el-form-item>
            <el-form-item label="备注" prop="memo">
              <el-input
                v-model="form.memo"
                type="textarea"
                :rows="2"
                placeholder="请输入内容"
              />
            </el-form-item>
            <el-form-item label="权限路由" prop="sort">
              <template slot="label">
                权限路由
                <el-tooltip class="item" effect="dark" content="选择权限关联的路由信息，可通过菜单栏直接关联页面所有需的路由，也可以细化为对应操作按钮所需的路由（需要前端配合权限控制）" placement="bottom-start">
                  <i class="el-icon-question" />
                </el-tooltip>
              </template>
              <el-select v-model="form.routes" multiple placeholder="请选择" style="width: 100%" filterable clearable>
                <el-option
                  v-for="item in routes"
                  :key="item.path"
                  :label="`${item.path} ${item.summary}`"
                  :value="item.path"
                >
                  <span>{{ item.path }}</span>
                  <span style="margin-left: 30px; color: #8492a6; font-size: 13px">{{ item.summary }}</span>
                </el-option>
              </el-select>
            </el-form-item>
          </el-form>
        </div>
        <div class="demo-drawer__footer">
          <el-button v-waves style="width: 260px;" @click="formVisible = false">关闭</el-button>
          <el-button v-if="form.id === 0" v-permission="['action:system:permission:create']" v-waves type="primary" style="width: 260px;" @click="submitCreate()">确认新增</el-button>
          <el-button v-else v-permission="['action:system:permission:update']" v-waves type="primary" style="width: 260px;" @click="submitUpdate()">确认修改</el-button>
        </div>
      </div>
    </el-drawer>
  </div>
</template>

<script>
import { createPermission, deletePermission, getPermissionTree, updatePermission } from '@/api/system/permission'
import { getRoutes } from '@/api/system/auth'
import { treeFormatEmpty } from '@/utils'
import clipboard from '@/utils/clipboard'

export default {
  name: 'SystemPermissionIndex',
  components: { },
  data() {
    return {
      tree: [],
      treeDefaultExpand: false,
      listLoading: false,
      listQuery: {
      },
      selectedIds: [],
      formTitle: '新增',
      formVisible: false,
      parentNode: {},
      form: {
        id: 0,
        type: 1,
        parent_id: 0,
        name: '',
        code: '',
        sort: 0,
        memo: '',
        routes: []
      },
      rules: {
        type: [
          { required: true, message: '请输入', trigger: 'blur' }
        ],
        parent_id: [
          { required: true, message: '请输入', trigger: 'blur' }
        ],
        name: [
          { required: true, message: '请输入', trigger: 'blur' }
        ],
        code: [
          { required: true, message: '请输入', trigger: 'blur' }
        ]
      },
      drawerForm: {},
      labelTypeClassMap: {
        1: 'primary',
        2: 'success'
      },
      labelTypeTextMap: {
        1: '菜单栏',
        2: '权限项'
      },
      routes: [],
      drawerLoading: false,
      loadingDrawerSubmit: false
    }
  },
  computed: {
  },
  created() {
    this.getList()
  },
  methods: {
    getList() {
      getPermissionTree(this.listQuery).then(res => {
        this.tree = treeFormatEmpty(res.tree)
      })
      this.getRoutes()
    },
    getRoutes() {
      getRoutes().then(res => {
        this.routes = res.routes ?? []
      })
    },
    resetFormData() {
      this.form = {
        id: 0,
        type: 1,
        parent_id: 0,
        name: '',
        code: '',
        sort: 0,
        memo: '',
        routes: []
      }
    },
    clickCreate() {
      this.resetFormData()
      this.formTitle = '新增'
      this.formVisible = true
      this.parentNode = {}
    },
    submitCreate() {
      this.$refs['refForm'].validate((valid) => {
        if (valid) {
          createPermission(this.form).then(res => {
            this.getList()
            this.$message({
              message: '创建成功',
              type: 'success'
            })
            this.formVisible = false
          }).then(res => {
          })
        }
      })
    },
    jsonRoutes(routes) {
      if (routes) {
        return JSON.parse(routes)
      }
      return []
    },
    clickUpdate(item) {
      this.form = {
        id: item.id,
        type: item.type,
        parent_id: item.parent_id,
        name: item.name,
        code: item.code,
        sort: item.sort,
        memo: item.memo,
        routes: []
      }
      if (item.routes) {
        this.form.routes = this.jsonRoutes(item.routes)
      }
      this.formTitle = '编辑'
      this.formVisible = true
      this.$nextTick(() => {
        this.parentNode = this.$refs.cascader.getCheckedNodes()[0].data ?? {}
      })
    },
    submitUpdate() {
      this.$refs['refForm'].validate((valid) => {
        if (valid) {
          updatePermission(this.form).then(res => {
            this.getList()
            this.$message({
              message: '编辑成功',
              type: 'success'
            })
            this.formVisible = false
          }).then(res => {
          })
        }
      })
    },
    clickDelete(item) {
      if (item.children && item.children.length > 0) {
        this.$message({ message: '存在子权限项，无法删除', type: 'error' })
        return
      }
      this.$confirm(`此操作将永久删除权限项[${item.name}], 是否继续?`, '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        this.submitDelete(item.id)
      }).catch(() => {
        this.$message({
          type: 'info',
          message: '已取消删除'
        })
      })
    },
    submitDelete(id) {
      deletePermission({ id: id }).then(res => {
        this.getList()
        this.$message({
          message: '删除成功',
          type: 'success'
        })
        this.formVisible = false
      }).then(res => {
      })
    },
    handleSelectionChange(val) {
      if (val.length) {
        const ids = []
        val.forEach(function(item) {
          ids.push(item.id)
        })
        this.selectedIds = ids
      } else {
        this.selectedIds = []
      }
    },
    cascaderChange(val) {
      // const typeName = this.form.type === 1 ? '' : 'action:'
      // this.form.code = typeName + node.code + ':'
      this.parentNode = this.$refs.cascader.getCheckedNodes()[0].data ?? {}
    },
    generateParentNodeItem(node) {
      return `<el-tag effect="dark" size="mini">${node.name} - ${node.code}</el-tag>`
    },
    clickSwitchExpand(status) {
      this.treeDefaultExpand = status
      this.tree.forEach(v => {
        this.expandRowRecursive(v, status)
      })
    },
    // 递归展开/收起行
    expandRowRecursive(row, expand) {
      this.$refs.refTreeTable.toggleRowExpansion(row, expand)
      if (row.children) {
        row.children.forEach(child => {
          this.expandRowRecursive(child, expand)
        })
      }
    },
    handleCopy(text, event) {
      clipboard(text, event)
    }
  }
}
</script>
